﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using TouchDriver.Data;
using System.IO.Ports;


namespace TouchDriver
{
    public class ComReader
    {
        private static ComReader instance = null;
        private SerialPort serialPort;
        private Record[] lastRecords = new Record[5];
        private DataProcess dataProcess = new DataProcess();

        //鼠标左击事件
        public delegate void MouseClickHandler(Location loc);
        public event MouseClickHandler MouseClickEvent;

        //一个手指移动事件
        public delegate void SingleMoveHandler(Location begin, Location end);
        public event SingleMoveHandler SingleMoveEvent;

        //两个手指移动事件
        public delegate void DoubleMoveHandler(Record begin, Record end);
        public event DoubleMoveHandler DoubleMoveEvent;


        private ComReader()
        {
            for (int i = 0; i < 5; ++i)
            {
                lastRecords[i] = new Record(0, 0, 0, 0);
            }

            //初始化串口
            serialPort = new SerialPort("COM1");
            serialPort.DataReceived += new SerialDataReceivedEventHandler(serialPort_DataReceived);
        }

        private void serialPort_DataReceived(object sender, SerialDataReceivedEventArgs e)
        {
            try
            {
                while(serialPort.BytesToRead > 0)
                {
                    string line = serialPort.ReadLine();
                    string[] nums = line.Split(new char[] { ',', '\0'}, StringSplitOptions.RemoveEmptyEntries);
                    if (nums == null || nums.Length != 4)
                        continue;

                    Record record = new Record(Convert.ToInt32(nums[0]), Convert.ToInt32(nums[1]),
                                                Convert.ToInt32(nums[2]), Convert.ToInt32(nums[3]));

                    //将记录循环向前移动，最新加入的始终是第五条记录
                    for (int i = 0; i < lastRecords.Length - 1; ++i)
                    {
                        lastRecords[i] = lastRecords[i + 1];
                    }

                    lastRecords[lastRecords.Length - 1] = ComToCM(record);
                    RecognizeGesture();
                }
            }
            catch (Exception ex)
            {
                Console.WriteLine(ex.Message.ToString());
            }
        }

        public static ComReader GetInstance()
        {
            if(instance == null)
            {
                instance = new ComReader();
            }
            return instance;
        }

        /// <summary>
        /// 将串口数据转换成厘米
        /// </summary>
        /// <param name="rd"></param>
        /// <returns></returns>
        public Record ComToCM(Record rd)
        {
            Record result = new Record();

            Vector2 loc1 = dataProcess.GetPosition(rd.loc1.x, rd.loc1.y);
            Vector2 loc2 = dataProcess.GetPosition(rd.loc2.x, rd.loc2.y);

            result.loc1 = new Location((int)loc1._x, (int)loc1._y);
            result.loc2 = new Location((int)loc2._x, (int)loc2._y);

            return result;
        }

        /// <summary>
        /// 根据缓冲区中的最近5条记录判断手势
        /// 并触发相应的事件
        /// </summary>
        private void RecognizeGesture()
        {
            //TODO 有待优化
            if (lastRecords[3].Valid && !lastRecords[4].Valid)
            {
                if (lastRecords[3].loc1.Valid)
                {
                    if(MouseClickEvent != null)
                        MouseClickEvent(lastRecords[3].loc1);
                }
                else
                {
                    if (MouseClickEvent != null)
                        MouseClickEvent(lastRecords[3].loc2);
                }
            }
            else if (lastRecords[3].Valid && lastRecords[4].Valid)
            {
                if (lastRecords[4].loc1.Valid && lastRecords[4].loc2.Valid &&
                    lastRecords[3].loc1.Valid && lastRecords[3].loc2.Valid)
                {
                    if(DoubleMoveEvent != null)
                        DoubleMoveEvent(lastRecords[3], lastRecords[4]);
                }
                else if (lastRecords[4].loc1.Valid && lastRecords[3].loc1.Valid)
                {
                    if(SingleMoveEvent != null)
                        SingleMoveEvent(lastRecords[3].loc1, lastRecords[4].loc1);
                }
                else if (lastRecords[4].loc2.Valid && lastRecords[3].loc2.Valid)
                {
                    if (SingleMoveEvent != null)
                        SingleMoveEvent(lastRecords[3].loc2, lastRecords[4].loc2);
                }
            }
        }

        /// <summary>
        /// 打开串口开始读取数据
        /// </summary>
        public void Start()
        {
            try
            {
                if (!serialPort.IsOpen)
                {
                    serialPort.Open();
                }
            }
            catch
            {
            }
        }

    }
}
